<?php

namespace App\App\Services;

use App\Models\Activity\ActivityService;
use App\Models\Enroll\Enroll;
use Illuminate\Support\Arr;

class ApplyService
{
    protected $activity;
    protected $canRepeat;
    protected $widgets = [];
    protected $records = [];

    public function __construct(ActivityService $activityService)
    {
        $this->activity = $activityService;
    }

    public function signed($activities_id, $mobile)
    {
        return Enroll::query()->where(compact('activities_id', 'mobile'))->exists();
    }

    public function analysisRules($activityId)
    {
        $widgets = $this->getWidgets($activityId);

        $rules = $messages = [];

        foreach ($widgets as $widget) {
            if (Arr::get($widget, 'required')) {
                $key = Arr::get($widget, 'name');
                $rules[$key] = 'required';
                $messages[sprintf('%s.required', $key)] = sprintf(
                    '%s不能为空',
                    Arr::get($widget, 'text')
                );
            }
        }

        if (Arr::get($rules, 'upload_content') == 'required') {
            $rules['upload_content'] = 'required|array';
        } else {
            $rules['upload_content'] = 'array';
        }

        $messages['upload_content.array'] = 'upload_content必须是数组';
        $rules['mobile'] = ['required', 'regex:/^1\d{10}$/'];
        $messages['mobile.required'] = '手机号码不能为空';
        $messages['mobile.regex'] = '手机号码格式不正确';

        return [$this->canRepeat, $rules, $messages];
    }

    public function getWidgets($activityId)
    {
        if (isset($this->widgets[$activityId])) {
            return $this->widgets[$activityId];
        }

        $activity = $this->getOne($activityId);

        if (null === $activity) {
            return [];
        }

        if (!$activity->rule) {
            return [];
        }

        $config = \GuzzleHttp\json_decode($activity->rule, true);
        $this->canRepeat = Arr::get($config, 'repeatedOn') == 'on';

        $default = [
            [
                'name' => 'name',
                'type' => 'text',
                'text' => '姓名',
                'required' => Arr::get($config, 'defaultName') == 'on',
            ],
            [
                'name' => 'mobile',
                'type' => 'text',
                'text' => '手机号码',
                'required' => true,
            ],
        ];

        if (Arr::get($config, 'upContentOn') == 'on') {
            $allowFiles = [
                'video' => '视频',
                'image' => '图片',
                'voice' => '音频',
            ];

            $fileType = Arr::get($config, 'upContentType');

            $default[] = [
                'name' => 'upload_content',
                'type' => 'file',
                'text' => Arr::get($allowFiles, $fileType),
                'required' => true,
                'file_type' => $fileType,
                'max_allow_upload' => Arr::get($config, 'upContentNum'),
            ];
        }

        $radios = $this->configToElement($config, 'radio', 'radio');
        $checkbox = $this->configToElement($config, 'select', 'checkbox');
        $selects = $this->configToElement($config, 'selectdown', 'select');
        $texts = $this->configToElement($config, 'text', 'text');
        $uploads = $this->configToElement($config, 'upload', 'file');
        $textAreas = $this->configToElement($config, 'textarea', 'textarea');

        $this->widgets[$activityId] = array_merge($default, $radios, $checkbox, $selects, $texts, $uploads, $textAreas);

        return $this->widgets[$activityId];
    }

    public function needUploadVideo($activityId)
    {
        $activity = $this->getOne($activityId);

        if (null === $activity) {
            return false;
        }

        $rules = json_decode($activity->rule, true);

        return Arr::get($rules, 'upContentType') == 'video';
    }

    public function getUploadFields($activityId)
    {
        $widgets = $this->getWidgets($activityId);
        $fields = [];

        foreach ($widgets as $widget) {
            if (Arr::get($widget, 'type') == 'file') {
                $fields[] = Arr::get($widget, 'name');
            }
        }

        return $fields;
    }

    public function getOne($activityId)
    {
        if (!isset($this->records[$activityId])) {
            $record = $this->activity->findOne($activityId);

            if (null === $record) {
                return null;
            }

            $this->records[$activityId] = $record;
        }

        return $this->records[$activityId];
    }

    protected function configToElement($configs, $column, $type)
    {
        $_configs = Arr::get($configs, $column, []);
        $elements = [];

        foreach ($_configs as $flag => $config) {
            $elements[] = [
                'name' => sprintf('%s_%s', $column, $flag),
                'type' => $type,
                'text' => Arr::get($config, 'value', '--'),
                'required' => isset($config['must']),
                'options' => array_values(Arr::get($config, 'option', [])),
            ];
        }

        return $elements;
    }
}
